package com.tanhua.manage.service;

import cn.hutool.core.date.DateUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.tanhua.manage.domain.AnalysisByDay;
import com.tanhua.manage.mapper.AnalysisByDayMapper;
import com.tanhua.manage.mapper.LogMapper;
import com.tanhua.manage.util.ComputeUtil;
import com.tanhua.manage.vo.AnalysisSummaryVo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;

import java.text.SimpleDateFormat;
import java.util.Date;

@Service
public class SummaryService extends ServiceImpl<AnalysisByDayMapper, AnalysisByDay> {

    @Autowired
    private AnalysisByDayMapper analysisByDayMapper;

    @Autowired
    private LogMapper logMapper;


    //概要统计信息业务
    public ResponseEntity<Object> showSummary() {
        //获得总用户数
        AnalysisByDay one = query().select("sum(num_registered) num_registered").one();
        Integer numRegistered = one.getNumRegistered();

        //获取当前日期
        Date date = new Date();
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        String dateTime = sdf.format(date);

        //今日新增用户数
        AnalysisByDay today = query().eq("record_date", dateTime).one();
        Integer newUsersToday = today.getNumRegistered();

        //今日登录数
        Integer loginTimesToday = today.getNumLogin();

        //今日活跃数
        Integer activeUsersToday = today.getNumActive();

        //昨日数据
        AnalysisByDay yesterday = query().eq("record_date", ComputeUtil.offsetDay(date, -1)).one();
        //昨日新增用户数
        Integer newUsersYesterday = yesterday.getNumRegistered();

        //昨日登录数
        Integer loginTimesYesterday = yesterday.getNumLogin();

        //昨日活跃数
        Integer activeUsersYesterday = yesterday.getNumActive();

        //过去七天活跃用户
        Long in7Days = this.getBaseMapper().findBetweenDate(ComputeUtil.offsetDay(date, -7), dateTime);

        //过去三十天活跃用户
        Long in30Days = this.getBaseMapper().findBetweenDate(ComputeUtil.offsetDay(date, -30), dateTime);

        AnalysisSummaryVo vo = new AnalysisSummaryVo();
        vo.setCumulativeUsers(numRegistered.longValue());
        vo.setActivePassMonth(in30Days);
        vo.setActivePassWeek(in7Days);
        vo.setNewUsersToday(newUsersToday.longValue());
        vo.setNewUsersTodayRate(ComputeUtil.computeRate(newUsersToday, newUsersYesterday));
        vo.setLoginTimesToday(loginTimesToday.longValue());
        vo.setLoginTimesTodayRate(ComputeUtil.computeRate(loginTimesToday, loginTimesYesterday));
        vo.setActiveUsersToday(activeUsersToday.longValue());
        vo.setActiveUsersTodayRate(ComputeUtil.computeRate(activeUsersToday, activeUsersYesterday));

        return ResponseEntity.ok(vo);

    }

    //定时任务统计业务
    public void analysis() {
        // 1.获取当前时间，默认转为yyyy-MM-dd
        String now = DateUtil.formatDate(new Date());

        // 2.根据当前时间，查询统计分析表数据: tb_analysis_by_day
        QueryWrapper<AnalysisByDay> query = new QueryWrapper<>();
        query.eq("record_date", now);
        AnalysisByDay analysis = analysisByDayMapper.selectOne(query);

        // 3.如果第一次统计，创建一条今日的统计数据
        if(analysis == null){
            analysis = new AnalysisByDay();
            // 当前时间对象, 这样Date就不包含时分秒，数据库要求没时分秒
            Date nowDate = DateUtil.parse(now);
            analysis.setCreated(nowDate);
            analysis.setUpdated(nowDate);
            analysis.setRecordDate(nowDate);
            analysisByDayMapper.insert(analysis);
        }

        // 昨天的日期
        String yes = ComputeUtil.offsetDay(new Date(), -1);

        // 4.统计
        // 4.1 统计log表中，今日注册人数
        Long newUserToday = logMapper.queryNewUserToday(now, "0102");

        // 4.2 统计log表中，登陆次数
        Long loginToday = logMapper.queryNewUserToday(now, "0101");

        // 4.3 统计log表中，活跃用户数
        Long activeToday = logMapper.queryActiveUser(now);

        // 4.4 统计log表中，次日留存用户数
        Long retention = logMapper.queryRetention1d(now, yes);

        // 5.封装数据，更新统计分析表
        analysis.setRecordDate(new Date());
        analysis.setNumRegistered(newUserToday.intValue());
        analysis.setNumActive(activeToday.intValue());
        analysis.setNumLogin(loginToday.intValue());
        analysis.setNumRetention1d(retention.intValue());
        analysis.setUpdated(new Date());

        analysisByDayMapper.updateById(analysis);

    }
}
